/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package co.springtree.spectrum.orm.controller;

import co.springtree.spectrum.orm.controller.exceptions.NonexistentEntityException;
import co.springtree.spectrum.orm.controller.exceptions.PreexistingEntityException;
import java.io.Serializable;
import javax.persistence.Query;
import javax.persistence.EntityNotFoundException;
import javax.persistence.criteria.CriteriaQuery;
import javax.persistence.criteria.Root;
import co.springtree.spectrum.orm.entities.Rule;
import co.springtree.spectrum.orm.entities.Command;
import co.springtree.spectrum.orm.entities.CommandRule;
import java.util.List;
import javax.persistence.EntityManager;
import javax.persistence.EntityManagerFactory;

/**
 *
 * @author Ricardo
 */
public class CommandRuleJpaController implements Serializable {

    public CommandRuleJpaController(EntityManagerFactory emf) {
        this.emf = emf;
    }
    private EntityManagerFactory emf = null;

    public EntityManager getEntityManager() {
        return emf.createEntityManager();
    }

    public void create(CommandRule commandRule) throws PreexistingEntityException, Exception {
        EntityManager em = null;
        try {
            em = getEntityManager();
            em.getTransaction().begin();
            Rule ruleId = commandRule.getRuleId();
            if (ruleId != null) {
                ruleId = em.getReference(ruleId.getClass(), ruleId.getRuleId());
                commandRule.setRuleId(ruleId);
            }
            Command commandId = commandRule.getCommandId();
            if (commandId != null) {
                commandId = em.getReference(commandId.getClass(), commandId.getCommandId());
                commandRule.setCommandId(commandId);
            }
            em.persist(commandRule);
            if (ruleId != null) {
                ruleId.getCommandRuleCollection().add(commandRule);
                ruleId = em.merge(ruleId);
            }
            if (commandId != null) {
                commandId.getCommandRuleCollection().add(commandRule);
                commandId = em.merge(commandId);
            }
            em.getTransaction().commit();
        } catch (Exception ex) {
            if (findCommandRule(commandRule.getCommandruleId()) != null) {
                throw new PreexistingEntityException("CommandRule " + commandRule + " already exists.", ex);
            }
            throw ex;
        } finally {
            if (em != null) {
                em.close();
            }
        }
    }

    public void edit(CommandRule commandRule) throws NonexistentEntityException, Exception {
        EntityManager em = null;
        try {
            em = getEntityManager();
            em.getTransaction().begin();
            CommandRule persistentCommandRule = em.find(CommandRule.class, commandRule.getCommandruleId());
            Rule ruleIdOld = persistentCommandRule.getRuleId();
            Rule ruleIdNew = commandRule.getRuleId();
            Command commandIdOld = persistentCommandRule.getCommandId();
            Command commandIdNew = commandRule.getCommandId();
            if (ruleIdNew != null) {
                ruleIdNew = em.getReference(ruleIdNew.getClass(), ruleIdNew.getRuleId());
                commandRule.setRuleId(ruleIdNew);
            }
            if (commandIdNew != null) {
                commandIdNew = em.getReference(commandIdNew.getClass(), commandIdNew.getCommandId());
                commandRule.setCommandId(commandIdNew);
            }
            commandRule = em.merge(commandRule);
            if (ruleIdOld != null && !ruleIdOld.equals(ruleIdNew)) {
                ruleIdOld.getCommandRuleCollection().remove(commandRule);
                ruleIdOld = em.merge(ruleIdOld);
            }
            if (ruleIdNew != null && !ruleIdNew.equals(ruleIdOld)) {
                ruleIdNew.getCommandRuleCollection().add(commandRule);
                ruleIdNew = em.merge(ruleIdNew);
            }
            if (commandIdOld != null && !commandIdOld.equals(commandIdNew)) {
                commandIdOld.getCommandRuleCollection().remove(commandRule);
                commandIdOld = em.merge(commandIdOld);
            }
            if (commandIdNew != null && !commandIdNew.equals(commandIdOld)) {
                commandIdNew.getCommandRuleCollection().add(commandRule);
                commandIdNew = em.merge(commandIdNew);
            }
            em.getTransaction().commit();
        } catch (Exception ex) {
            String msg = ex.getLocalizedMessage();
            if (msg == null || msg.length() == 0) {
                Integer id = commandRule.getCommandruleId();
                if (findCommandRule(id) == null) {
                    throw new NonexistentEntityException("The commandRule with id " + id + " no longer exists.");
                }
            }
            throw ex;
        } finally {
            if (em != null) {
                em.close();
            }
        }
    }

    public void destroy(Integer id) throws NonexistentEntityException {
        EntityManager em = null;
        try {
            em = getEntityManager();
            em.getTransaction().begin();
            CommandRule commandRule;
            try {
                commandRule = em.getReference(CommandRule.class, id);
                commandRule.getCommandruleId();
            } catch (EntityNotFoundException enfe) {
                throw new NonexistentEntityException("The commandRule with id " + id + " no longer exists.", enfe);
            }
            Rule ruleId = commandRule.getRuleId();
            if (ruleId != null) {
                ruleId.getCommandRuleCollection().remove(commandRule);
                ruleId = em.merge(ruleId);
            }
            Command commandId = commandRule.getCommandId();
            if (commandId != null) {
                commandId.getCommandRuleCollection().remove(commandRule);
                commandId = em.merge(commandId);
            }
            em.remove(commandRule);
            em.getTransaction().commit();
        } finally {
            if (em != null) {
                em.close();
            }
        }
    }

    public List<CommandRule> findCommandRuleEntities() {
        return findCommandRuleEntities(true, -1, -1);
    }

    public List<CommandRule> findCommandRuleEntities(int maxResults, int firstResult) {
        return findCommandRuleEntities(false, maxResults, firstResult);
    }

    private List<CommandRule> findCommandRuleEntities(boolean all, int maxResults, int firstResult) {
        EntityManager em = getEntityManager();
        try {
            CriteriaQuery cq = em.getCriteriaBuilder().createQuery();
            cq.select(cq.from(CommandRule.class));
            Query q = em.createQuery(cq);
            if (!all) {
                q.setMaxResults(maxResults);
                q.setFirstResult(firstResult);
            }
            return q.getResultList();
        } finally {
            em.close();
        }
    }

    public CommandRule findCommandRule(Integer id) {
        EntityManager em = getEntityManager();
        try {
            return em.find(CommandRule.class, id);
        } finally {
            em.close();
        }
    }

    public int getCommandRuleCount() {
        EntityManager em = getEntityManager();
        try {
            CriteriaQuery cq = em.getCriteriaBuilder().createQuery();
            Root<CommandRule> rt = cq.from(CommandRule.class);
            cq.select(em.getCriteriaBuilder().count(rt));
            Query q = em.createQuery(cq);
            return ((Long) q.getSingleResult()).intValue();
        } finally {
            em.close();
        }
    }
    
}
